package modele;

import java.awt.Color;
import java.io.Serializable;
import java.util.Enumeration;
import java.util.Vector;

public class Polygone extends FormeGeometrique implements Serializable {

	private Vector<Point> lesPoints;
	private boolean is_closed = true;//boolean qui permet de savoir si le polygone est fermé ou non

	// Constructeur par défaut
	public Polygone() {
		this.lesPoints = new Vector<Point>();
	}

	// Constructeur canonique
	public Polygone(Vector<Point> argument, boolean statusclosed) {
		this.lesPoints = argument;
		this.is_closed = statusclosed;
	}

	public Polygone(Vector<Point> argument, boolean statusclosed, Color c) {
		this.lesPoints = argument;
		this.is_closed = statusclosed;
		this.couleur = c;
	}
	
	// Getters (Accesseurs)
	public Vector<Point> getListPoints() {
		return lesPoints;
	}
	
	public boolean getCosed(){
		return this.is_closed;
	}

	public int getSize() {
		int size = lesPoints.size();
		return size;
	}

	// Setters (Mutateurs)
	public void setListPoints(Vector<Point> listPoints) {
		this.lesPoints = listPoints;
	}
	
	public void setClosed(boolean valeur){
		this.is_closed=valeur;
	}

	public void addPoint(Point sujet) {
		System.out.println("on add un point dans un polygone");
		this.lesPoints.addElement(sujet.createClone());
	}

	public void removePoint(Point sujet) {
		System.out.println("on remove un point!");
		this.lesPoints.removeElement(sujet);
	}

	public String toString() {
		String rapport = new String("---------------------------------------------------------\n");
		rapport += "toString du Polygone : ";
		if (this.is_closed) {rapport+="Ce Polygone est fermé, il est composé de "+this.lesPoints.size()+" point(s) :\n";}
		else {rapport+="(Ce Polygone est ouvert)\n";}
				
		Enumeration<Point> e1 = this.lesPoints.elements();
		while (e1.hasMoreElements()) {
			rapport += e1.nextElement().toString() + " \n ";
		}
		rapport += "---------------------------------------------------------";
		return rapport;
	}

	public boolean equals(FormeGeometrique p) {
		// d'abord on teste la taille...
		// si la taille est égale, il faut parcourir les 2 polygone et les
		// comparer point à point.
		boolean egal = true;
		Enumeration<Point> e1 = this.lesPoints.elements();
		Enumeration<Point> e2 = ((Polygone) p).lesPoints.elements();

		if (this.lesPoints.size() != ((Polygone) p).lesPoints.size())
			return false;
		else {
			while (e1.hasMoreElements() && egal)
			// on peut mettre qu'un seul hasMoreElements car les deux
			// énumérations ont la meme taille
			{
				Point p1 = e1.nextElement();
				Point p2 = e2.nextElement();
				// actualisation du boolean egal
				egal = p1.equals(p2);
			}
			return egal;
		}
	}

	@Override
	public Polygone createClone() {
		System.out.println("on crée un clone d'un polygone");
		Polygone res = new Polygone();
		Enumeration<Point> e = lesPoints.elements();
		while (e.hasMoreElements()) {
			res.addPoint(e.nextElement().createClone());
		}
		res.setCouleur(this.couleur);
		return res;
	}

	@Override
	public Polygone createSymetrieO() {
		Polygone res = new Polygone();
		Enumeration<Point> e = lesPoints.elements();
		while (e.hasMoreElements()) {
			res.addPoint(e.nextElement().createSymetrieO());
		}
		return res;
	}

	@Override
	//Le perimetre est calculé seulement si le Polygone est fermé et si il a + de 2 Points
	public double perimetre() {
		double perim = 0;
		if (this.is_closed == true && lesPoints.size() > 2) {
			
			int i=0;
			while (i<lesPoints.size()) {
				if(i == lesPoints.size()-1)
				{perim = perim + lesPoints.elementAt(i).distance(lesPoints.elementAt(0));}
				else
				{perim = perim + lesPoints.elementAt(i).distance(lesPoints.elementAt(i+1));}
				i++;
			}
		}
		return perim;
	}


	@Override
	public double surface() {
		return 0;
	}

	@Override
	public void symetrieO() {
		Enumeration<Point> e = lesPoints.elements();
		while (e.hasMoreElements()) {
			e.nextElement().symetrieO();
		}
	}

	@Override
	public void symetrieX() {
		Enumeration<Point> e = lesPoints.elements();
		while (e.hasMoreElements()) {
			e.nextElement().symetrieX();
		}

	}

	@Override
	public void symetrieY() {
		Enumeration<Point> e = lesPoints.elements();
		while (e.hasMoreElements()) {
			e.nextElement().symetrieY();
		}

	}

	@Override
	public void projectionX() {
		Enumeration<Point> e = lesPoints.elements();
		while (e.hasMoreElements()) {
			e.nextElement().projectionX();
		}

	}

	@Override
	public void projectionY() {
		Enumeration<Point> e = lesPoints.elements();
		while (e.hasMoreElements()) {
			e.nextElement().projectionY();
		}

	}

	public static void main(String[] args) {
		Point a = new Point(0, 0);
		Point b = new Point(0, 2);
		Point c = new Point(2, 2);
		Point d = new Point(2, 0);

		Polygone monPolygone = new Polygone();
		monPolygone.addPoint(a);
		monPolygone.addPoint(b);
		monPolygone.addPoint(c);
		monPolygone.addPoint(d);
		monPolygone.setClosed(true);
		System.out.println(monPolygone);
		System.out.println(monPolygone.getSize());

		// monPolygone.removePoint(c);
		// System.out.println(monPolygone);
		// System.out.println(monPolygone.getSize());


		System.out.println(monPolygone);
		System.out.println(monPolygone.perimetre());
		System.out.println("Test du clonage et du equals : ");
		Polygone clonePolygone = monPolygone.createClone();
		System.out.println(clonePolygone.equals(monPolygone));
		
	}

}
